package com.example.easyhttp;


import com.google.gson.Gson;
import com.google.gson.JsonArray;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import ohos.eventhandler.EventHandler;
import ohos.eventhandler.EventRunner;

import java.io.BufferedReader;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;

/**
 * Encapsulates a thread's callback operation
 *
 * @author ZZR ,program.java@qq.com
 * @version 1.0.0
 * @since 2020-10-3
 */
public abstract class EasyCallBack<T> {
    public static final int DATA_ERROR = 10000;
    public static final int NET_ERROR = 20000;
    public static final boolean SUCCESS = true;    // 成功

    public static Gson gson = new Gson();

    static EventHandler mMainHandler = new EventHandler(EventRunner.getMainEventRunner());

    public void onProgress(float progress, long total) {
    }

    void onError(final EasyResponse response) {

        final String errorMessage;
        if (response.inputStream != null) {
            errorMessage = getRetString(response.inputStream);
        } else if (response.errorStream != null) {
            errorMessage = getRetString(response.errorStream);
        } else if (response.exception != null) {
            errorMessage = response.exception.getMessage();
        } else {
            errorMessage = "";
        }
        mMainHandler.postTask(new Runnable() {
            @Override
            public void run() {
                onFailure(response.code, errorMessage);
            }
        });
    }

    void onSeccess(EasyResponse response) {
        final T obj = onParseResponse(response);

        if (obj == null) {
            onFailure(DATA_ERROR, "数据解析异常");

        }


        mMainHandler.postTask(new Runnable() {
            @Override
            public void run() {
                onResponse(obj);
            }
        });
    }


    public abstract T onParseResponse(EasyResponse response);


    public abstract void onFailure(int code, String errorMessage);


    public abstract void onResponse(T response);

    public abstract static   class CallBackObject<T> extends EasyCallBack<T> {
        @Override
        public T onParseResponse(EasyResponse response) {

            T data =null;
            // 把返回流改为字符流
            String jsonstr = getRetString(response.inputStream);
            JsonObject jsonObject = new JsonParser().parse(jsonstr).getAsJsonObject();
            // 获取接口返回当前时间
            Long jtime_point = jsonObject.getAsJsonPrimitive("time_point").getAsLong();
            // 获取请求是否成功
            boolean isSuccess = jsonObject.getAsJsonPrimitive("success").getAsBoolean();
            // 判断是否请求成功
            if(isSuccess)
            {
                // 判断是否包含data字段
                if (jsonObject.has("data")) {
                    // 判断data是否是集合，如果是，则按集合进行解析。否则按对象解析
                    if (jsonObject.get("data") instanceof JsonArray) {
                        JsonArray jsonArray = jsonObject.getAsJsonArray("data");
                        data= (T) gson.fromJson(jsonObject, getGenericClass());
                    } else {
                        JsonObject jobjData = jsonObject.getAsJsonObject("data");
                        data= (T) gson.fromJson(jobjData, getGenericClass());
                    }
                }
            }
            return data;
        }
        @SuppressWarnings("unchecked")
        private Class<T> getGenericClass() {
            Type type = getClass().getGenericSuperclass();
            Type[] arguments = ((ParameterizedType) type).getActualTypeArguments();
            return (Class<T>) arguments[0];
        }
    }




    public static abstract class CallBackDefault extends EasyCallBack<EasyResponse> {
        @Override
        public EasyResponse onParseResponse(EasyResponse response) {
            return response;
        }
    }


    public static abstract class CallBackString extends EasyCallBack<String> {
        @Override
        public String onParseResponse(EasyResponse response) {
            try {
                return getRetString(response.inputStream);
            } catch (Exception e) {
                throw new RuntimeException("failure");
            }
        }
    }

    private static String getRetString(InputStream is) {
        String buf;
        try {
            BufferedReader reader = new BufferedReader(new InputStreamReader(is, "utf-8"));
            StringBuilder sb = new StringBuilder();
            String line = "";
            while ((line = reader.readLine()) != null) {
                sb.append(line + "\n");
            }
            is.close();
            buf = sb.toString();
            return buf;

        } catch (Exception e) {
            return null;
        }
    }

}
